﻿using DataAcquisition.CustomControls;
using DataAcquisition;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using gl_SMT.Model;
using SMTUploadProductionData.model;
using System.Data;
using System;
using gl_SMT.View;
using System.Windows.Threading;

namespace gl_SMT
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
            this.Loaded += MainWindow_Loaded;
            EventHub.TabRequested += OnTabRequested; ;
        }

        List<string> list_DvName = new List<string>();//设备名称
        List<DeviceType> lsit_devicetype = new List<DeviceType>();//机台类型自定义控件
        DatabaseReadWrite Database ;
        string str_ConnectData;
        
        private void MainWindow_Loaded(object sender, RoutedEventArgs e)
        {
            Database = new DatabaseReadWrite(ref str_ConnectData);//连接数据库
            if (str_ConnectData != null)
            {
                MessageBox.Show("无法连接数据库");//连接失败
                return;
            }
            AddCustomControls();// 添加自定义控件
            Task.Run(() => DataAdd());//数据添加
        }

        /// <summary>
        /// 添加自定义控件
        /// </summary>
        private void AddCustomControls()
        {
            DeviceTypeName device = new DeviceTypeName();
            list_DvName.Add(device.gkg_Printing);
            list_DvName.Add(device.hl_Printing);
            list_DvName.Add(device.ymh_Mounter);
            list_DvName.Add(device.juki_Patch);
            for (int i = 0; i < list_DvName.Count; i++)
            {
                DeviceType deviceType = new DeviceType();//添加自定义控件
                deviceType.DeviceName = list_DvName[i];//设备名称
                deviceType.DeviceNumber = GetDNumber(list_DvName[i]).ToString();//在线的数量
                deviceType.closeMainWindow = TabConrolAdd;//绑定委托事件
                deviceType.Margin = new Thickness(0, 20, 0, 0);//自定义控件的间距
                wrapPanel_Device.Children.Add(deviceType);//添加到wrapPanel
                lsit_devicetype.Add(deviceType);//添加到List<DeviceType>方便后续的数据更新
            }
        }

        /// <summary>
        /// 添加机台类型选项卡
        /// </summary>
        public void TabConrolAdd()
        {
            HideTabItem();
            TabItem tab_conrol = new TabItem();//初始化一个选项卡
            tab_conrol.Width = 150;//选项卡的表头宽度
            tab_conrol.Height = 30;//选项卡的表头高度
            tab_conrol.Style = FindResource("ClosableTabItemStyle") as Style;//绑定样式
            tab_conrol.Header = VariableStorage.SelectType;//表头名称
            UserControlMachine Machine = new UserControlMachine();
            tab_conrol.Content = Machine;//绑定自定义控件

            bool isDuplicate = false;
            for (int i = 0; i < tabControl_Main.Items.Count; i++)//遍历全部选项卡
            {
                var existingTabItem = tabControl_Main.Items[i] as TabItem;
                if (existingTabItem != null && tab_conrol.Header != null && existingTabItem.Header.ToString() == tab_conrol.Header.ToString())//判断是否已经添加过选项卡 
                {
                    isDuplicate = true;
                    tabControl_Main.SelectedItem = existingTabItem;
                    break;
                }
            }
            if (isDuplicate ==false) //如果没有添加过该名称的选项卡就添加否则就不添加
            {
                tabControl_Main.Items.Add(tab_conrol);//添加选项卡
                tabControl_Main.SelectedItem = tab_conrol;//索引到添加的选项卡
            }
        }

        /// <summary>
        /// 添加机台数据查询选项卡
        /// </summary>
        /// <param name="tabHeader"></param>
        private void OnTabRequested(string tabHeader)
        {
            HideTabItem();
            TabItem tab_conrol = new TabItem();
            tab_conrol.Width = 170;
            tab_conrol.Height = 30;
            tab_conrol.Style = FindResource("ClosableTabItemStyle") as Style;
            tab_conrol.Header = tabHeader;
            string? HeaderName = tab_conrol.Header.ToString();//表头名称
            if (HeaderName.Contains("GKG自动印刷机"))
            {
                gkg_DataSelect gkg_Control = new gkg_DataSelect();
                gkg_Control.MachineName = tabHeader;
                tab_conrol.Content = gkg_Control;
            }
            else if (HeaderName.Contains("回流焊接机"))
            {
                hl_DataSelect hl_Control = new hl_DataSelect();
                hl_Control.MachineName = tabHeader;
                tab_conrol.Content = hl_Control;
            }
            else if (HeaderName.Contains("雅马哈贴片机"))
            {
                ymh_DataSelect ymh_dataSelect = new ymh_DataSelect();
                ymh_dataSelect.MachineName = tabHeader;
                tab_conrol.Content = ymh_dataSelect;
            }
            else if (HeaderName.Contains("JUKI贴片机"))
            {
                juki_DataSelect juki_Dataselect = new juki_DataSelect();
                juki_Dataselect.MachineName = tabHeader;
                tab_conrol.Content = juki_Dataselect;
            }
            bool isDuplicate = false;
            for (int i = 0; i < tabControl_Main.Items.Count; i++)
            {
                var existingTabItem = tabControl_Main.Items[i] as TabItem;
                if (existingTabItem != null && tab_conrol.Header != null && existingTabItem.Header.ToString() == tab_conrol.Header.ToString())
                {
                    isDuplicate = true;
                    tabControl_Main.SelectedItem = existingTabItem;
                    break;
                }
            }
            if (isDuplicate == false)
            {
                tabControl_Main.Items.Add(tab_conrol);
                tabControl_Main.SelectedItem = tab_conrol;
            }
        }


        private void HideTabItem()
        {
            if (tabControl_Main.Items.Count>7)
            {
                Dispatcher.BeginInvoke(() => tabControl_Main.Items.RemoveAt(1));
                Dispatcher.BeginInvoke(() => tabControl_Main.Items.RemoveAt(2));
            }
        }

        public int GetDNumber(string Name)
        {
            int Number = 0;
            switch (Name)
            {
                case "GKG自动印刷机":
                    return Number = 12;
                case "点精点胶机":
                    return Number = 1;
                case "除湿房":
                    return Number = 6;
                case "富士贴片机":
                    return Number = 6;
                case "回流焊接机":
                    return Number = 3;
                case "丝印印刷机":
                    return Number = 1;
                case "雅马哈贴片机":
                    return Number = 6;
                case "JUKI贴片机":
                    return Number = 2;
                default:
                    return Number;
            }
        }
        
        private async Task DataAdd()
        {
            while (true)
            {
                try
                {
                    await Task.Run(() => gkg_DataUpdate(lsit_devicetype[0]));
                    await Task.Run(() => hl_DataUpdate(lsit_devicetype[1]));
                    await Task.Run(() => juki_DataUpdate(lsit_devicetype[3]));
                    await Task.Run(() => ymh_DataUpdate(lsit_devicetype[2]));
                }
                catch (Exception )
                {
                    continue;
                }
                await Task.Delay(5000);
            }
        }

        #region  GKG印刷机
        /// <summary>
        /// gkg数据更新
        /// </summary>
        /// <param name="device"></param>
        /// <returns></returns>
        private async Task gkg_DataUpdate(DeviceType device)
        {
            List<gkg_model> list_gkg = new List<gkg_model>();
            await Database.SelectDataAsync(list_gkg);
            int TotalOutput = 0;//总产量
            foreach (var gkg in list_gkg)
            {
                TotalOutput += gkg.PCBNumber;//计算总产量
            }
            List<string> machineNames = await Database.SelectDataAsync("gkg_Producedate", "TimeStamp");//查询在线数量
            int AlmNumber= await Database.SelectOPEventNumber();//查询报警数量
            double UPH = await gkg_UPH() / 60 / 60;//UPH计算
            
            await Dispatcher.Invoke(async () =>
            {
                device.txt_ProductionNumber.Text = machineNames.Count.ToString();//在线数量
                device.txt_AlmNumber.Text = AlmNumber.ToString();//总报警数量
                device.txt_OutPut.Text= TotalOutput.ToString();//总产量
                device.txt_Cycle.Text = await gkg_CycleTime();//生产周期
                device.txt_UPH.Text = (TotalOutput / UPH).ToString("0.0");
            });
        }

        /// <summary>
        /// gkg生产时间
        /// </summary>
        /// <returns></returns>
        private async Task<string> gkg_CycleTime()
        {
            TimeSpan timeSpan = TimeSpan.FromSeconds(0);//初始化一个时间
            List<string> list_Name = await Database.SelectColNameAsync("gkg_Producedate");//获取在线机台
            for (int i = 0; i < list_Name.Count; i++)
            {
                List<gkg_model> list_gkg = new List<gkg_model>();
                await Database.SelectDataAsync(list_gkg, "gkg_Producedate", "MachineName", list_Name[i]);//查询机台当天数据
                foreach (var gkg in list_gkg)
                {
                    timeSpan += TimeSpan.FromSeconds(int.Parse(gkg.CycleTime));//将所有的生产时间进行相加
                }
            }
            int totalHours = (int)timeSpan.TotalHours;//获取时间中的小时
            string formattedTime = $"{totalHours:D2}:{timeSpan.Minutes:D2}:{timeSpan.Seconds:D2}";//转换成时间格式
            return formattedTime.ToString();
        }

        /// <summary>
        /// 获取所有机台的单个的生产周期
        /// </summary>
        /// <returns></returns>
        private async Task<double> gkg_UPH()
        {
            List<string> list_MachineName= await Database.SelectColNameAsync("gkg_Producedate");//机台名称
            double dou_UPH = 0;
            for (int i = 0; i < list_MachineName.Count; i++)
            {
                DataTable dt = await Database.gkg_SelectDataAsync("gkg_Producedate", list_MachineName[i]);//查询数据库当天的数据
                if (dt.Rows.Count == 0) continue;
                foreach (DataRow item in dt.Rows)
                {
                    dou_UPH += double.Parse(item.ItemArray[9].ToString());
                }
            }
            return dou_UPH;
        }
        #endregion

        #region  回流焊接
        private async Task hl_DataUpdate(DeviceType device)
        {
            List<hl_model> list_hl = new List<hl_model>();
            await Database.SelectDataAsync(list_hl, "hl_Producedate", "MachineName", "1号机");
            List<string> machineNames = await Database.SelectDataAsync("hl_Producedate", "logTime");//查询在线数量
            Dispatcher.Invoke(() =>
            {
                device.txt_ProductionNumber.Text = machineNames.Count.ToString();//在线数量
                device.txt_AlmNumber.Text = "无";
                device.txt_OutPut.Text = "无";
                device.txt_Cycle.Text = "无";
                device.txt_UPH.Text = "无";
            });
        }
        #endregion

        #region 雅马哈
        private async Task ymh_DataUpdate(DeviceType device)
        {
            int PTotaNumber = await ymh_Productions("白班");//查询白班的生产数据
            int YTotaNumber= await ymh_Productions("夜班");//查询夜班的生产数据
            List<string> machineNames = await Database.SelectDataAsync("ymh_Producedate", "Time");//查询在线数量
            string CycleTime = await ymh_ProductionTime();//获取平均的生产周期
            int TotalQuantity = await ymh_HPU();//获取UPH
            double Htime = double.Parse(CycleTime.Split(':')[0]);
            double Mtime= double.Parse(CycleTime.Split(':')[1]);
            double totalTime = Htime + Mtime / 60;
            totalTime = TotalQuantity / totalTime;
            TotalQuantity = Convert.ToInt32(totalTime);
            Dispatcher.Invoke(() =>
            {
                device.txt_ProductionNumber.Text = machineNames.Count.ToString();//在线数量
                device.tb_Expected.Text = "白班总产量";
                device.txt_AlmNumber.Text = PTotaNumber.ToString();//总报警数量
                device.tb_Production.Text = "夜班总产量";
                device.txt_OutPut.Text = YTotaNumber.ToString();//总产量
                device.txt_Cycle.Text = CycleTime;
                device.txt_UPH.Text = TotalQuantity.ToString();
            });
        }

        /// <summary>
        /// 白、夜班总数
        /// </summary>
        /// <returns></returns>
        private async Task<int> ymh_Productions(string DayNight)
        {
            List<ymh_DayNightShifts_model> list_DayNightShift = new List<ymh_DayNightShifts_model>();
            int TotalNumber = 0;
            await Database.SelectDataAsync(list_DayNightShift, DayNight);
            foreach (var ymh in list_DayNightShift)
            {
                TotalNumber += ymh.TotalQuantity;
            }
            return TotalNumber;
        }

        /// <summary>
        /// 平均生产周期
        /// </summary>
        /// <returns></returns>
        private async Task<string> ymh_ProductionTime()
        {
            TimeSpan[] time=new TimeSpan[6];
            TimeSpan timeSpan = TimeSpan.Parse("0");
            List<string> list_Name = await Database.SelectColNameAsync("ymh_Producedate");//查询在线机台名称
            for (int i = 0; i < list_Name.Count; i++)
            {
                timeSpan = TimeSpan.Parse("0");//初始化一个时间
                List<ymh_model> list_ymh = new List<ymh_model>();
                await Database.SelectDataAsync(list_ymh, "ymh_Producedate", "MachineName", list_Name[i]);//查询机台类型当天的数据
                for (int j = 1; j < list_ymh.Count-1; j++)
                {
                    try
                    {
                        if (list_ymh[j].RunningStatus != "运行中") continue;
                        if (list_ymh[j].Time == list_ymh[j - 1].Time) continue;
                        timeSpan += TimeSpan.Parse(list_ymh[j + 1].Time.Split(' ')[1]) - TimeSpan.Parse(list_ymh[j].Time.Split(' ')[1]);//将所有的生产周期进行相加
                    }
                    catch (Exception ex)
                    {
                        continue;
                    }
                }
                time[i] = timeSpan;
            }
            timeSpan = TimeSpan.Parse("0");
            for (int j = 0; j < time.Length; j++)
            {
                timeSpan += time[j];
            }
            int totalHours = (int)timeSpan.TotalHours;
            string formattedTime = $"{totalHours:D2}:{timeSpan.Minutes:D2}:{timeSpan.Seconds:D2}";
            return formattedTime;
        }


        private async Task<int> ymh_HPU()
        {
            int TotalQuantity = 0;
            List<string> list_Name = await Database.SelectColNameAsync("ymh_Producedate");
            for (int i = 0; i < list_Name.Count; i++)
            {
                List<ymh_model> list_ymh = new List<ymh_model>();
                await Database.SelectDataAsync(list_ymh, "ymh_Producedate", "MachineName", list_Name[i]);
                for (int j = 1;  j < list_ymh.Count;  j++)
                {
                    try
                    {
                        if (list_ymh[j].TotalQuantity == "") continue;
                        if (int.Parse(list_ymh[j].TotalQuantity) < int.Parse(list_ymh[j - 1].TotalQuantity))
                        {
                            TotalQuantity += int.Parse(list_ymh[j - 1].TotalQuantity);
                        }
                        if (j == list_ymh.Count - 1)
                        {
                            TotalQuantity += int.Parse(list_ymh[j].TotalQuantity);
                        }
                    }
                    catch (Exception)
                    {
                        continue;
                    }
                }
            }
            return TotalQuantity;
        }
        #endregion

        #region  JUKI贴片机
        private async Task juki_DataUpdate(DeviceType device)
        {
            List<juki_model> list_juki = new List<juki_model>();
            await Database.SelectDataAsync(list_juki);
            List<string> machineNames = await Database.SelectDataAsync("juki_Producedate", "StartTime");//查询在线数量
            int TotaNumber = await juki_Production(list_juki);//生产总数
            int TotalPlace = await juki_Qualified(list_juki);//良品总数
            string RepairTime = await juki_CycleTime(list_juki);//运行时间
            string UPH = await juki_UPH(TotaNumber, RepairTime, machineNames.Count);
            Dispatcher.Invoke(() =>
            {
                device.txt_ProductionNumber.Text = machineNames.Count.ToString();//在线数量
                device.tb_Production.Text = "良品数量";
                device.txt_AlmNumber.Text = TotaNumber.ToString();//总产量
                device.tb_Expected.Text = "生产总数";
                device.txt_OutPut.Text = TotalPlace.ToString();//良品总数
                device.txt_Cycle.Text = RepairTime.ToString();//平均生产时间
                device.txt_UPH.Text = UPH.ToString();
            });
        }

        /// <summary>
        /// 生产总数
        /// </summary>
        /// <returns></returns>
        private Task<int> juki_Production(List<juki_model> juki_Models)
        {
            int TotalNumber = 0;
            foreach (var juki in juki_Models)
            {
                TotalNumber += juki.TotalPick;
            }
            return Task.FromResult(TotalNumber);
        }

        /// <summary>
        /// 良品总数
        /// </summary>
        /// <returns></returns>
        private Task<int> juki_Qualified(List<juki_model> juki_Models)
        {
            int TotalPlace = 0;
            foreach (var juki in juki_Models)
            {
                TotalPlace += juki.TotalPlace;
            }
            return Task.FromResult(TotalPlace);
        }

        private Task<string> juki_CycleTime(List<juki_model> juki_Models)
        {
            TimeSpan CycleTime=TimeSpan.Parse("0");
            foreach (var juki in juki_Models)
            {
                CycleTime += TimeSpan.Parse(juki.RunningTime);
            }
            return Task.FromResult<string>((CycleTime).ToString());
        }

        private Task<string> juki_UPH(int TNumber,string RTime,int OnlineQuantity)
        {
            double Htime = double.Parse(RTime.Split(':')[0]);
            double Mtime = double.Parse(RTime.Split(':')[1]);
            double totalTime = Htime + Mtime / 60;
            string Number = (TNumber / totalTime/ OnlineQuantity).ToString("0.0");
            return Task.FromResult(Number);
        }

        #endregion

        
    }
}